package dk.android.houseenabler.classes;

import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;

import android.os.Environment;

public class FileHandle {

	private String packageName = "dk.android.houseenabler";
	private String path;
	
	public FileHandle() {
		File sdDir = Environment.getExternalStorageDirectory();
		//System.out.println(sdDir.getAbsolutePath());
	    this.path = sdDir.getAbsolutePath() + "/Android/data/" + this.packageName + "/files";
	    
	    File file = new File(this.path);
        file.mkdirs();
	    //System.out.println(this.path);
	}
	
	public String getPath() {
		return this.path;
	}
	
	/**
	 * Helper Method to Test if external Storage is Available
	 */
	public boolean isExternalStorageAvailable() {
	    boolean state = false;
	    String extStorageState = Environment.getExternalStorageState();
	    if (Environment.MEDIA_MOUNTED.equals(extStorageState)) {
	        state = true;
	    }
	    return state; 
	}
	
	/**
	 * Helper Method to Test if external Storage is read only
	 */
	public boolean isExternalStorageReadOnly() {
	    boolean state = false;
	    String extStorageState = Environment.getExternalStorageState();
	    if (Environment.MEDIA_MOUNTED_READ_ONLY.equals(extStorageState)) {
	        state = true;
	    }
	    return state;
	}
	
	/**
	 * Write to external public directory
	 * @param filename - the filename to write to
	 * @param content - the content to write 
	 */
	public void writeDataToStorage(String filename, byte[] content) {

	    // API Level 7 or lower, use getExternalStorageDirectory() 
	    //  to open a File that represents the root of the external 
	    // storage, but writing to root is not recommended, and instead 
	    // application should write to application-specific directory, as shown below.

		//String packageName = this.getPackageName();

	    if (isExternalStorageAvailable() && 
	       !isExternalStorageReadOnly()) {
	        try {
	            File file = new File(this.path, filename);
	            //file.mkdirs();
	            FileOutputStream fos = new FileOutputStream(file);
	            fos.write(content);
	            fos.close();
	        } catch (FileNotFoundException e) {
	            e.printStackTrace();
	        } catch (IOException e) {
	            e.printStackTrace();
	        }
	    }
	}
	
	/**
	 * Write to external public directory
	 * @param filename - the filename to write to
	 * @param content - the content to write 
	 */
	public void writeObjectToStorage(String filename, Object content) {

	    // API Level 7 or lower, use getExternalStorageDirectory() 
	    //  to open a File that represents the root of the external 
	    // storage, but writing to root is not recommended, and instead 
	    // application should write to application-specific directory, as shown below.

		//String packageName = this.getPackageName();
		
	    if (isExternalStorageAvailable() && 
	       !isExternalStorageReadOnly()) {
	    	
	    	
	        try {
	            File file = new File(this.path, filename);
	            //file.mkdirs();
	            
	            FileOutputStream fos = new FileOutputStream(file);
	            ObjectOutputStream out = new ObjectOutputStream(fos);
	            
	            out.writeObject(content);
	            out.close();
	            
	        } catch (FileNotFoundException e) {
	            e.printStackTrace();
	        } catch (IOException e) {
	            e.printStackTrace();
	        }
	    }
	}
	
	/**
	 * Reads a file from internal storage
	 * @param filename - the filename to read from
	 * @return the file contents
	 */
	public byte[] readDataFromStorage(String filename) {
	    int len = 1024;
	    byte[] buffer = new byte[len];
	    //String packageName = this.getPackageName();


	    if (!isExternalStorageReadOnly()) {     
	        try {
	            File file = new File(this.path, filename);      
	            if(file.exists()) {
		            FileInputStream fis = new FileInputStream(file);
		            ByteArrayOutputStream baos = new ByteArrayOutputStream();
		            int nrb = fis.read(buffer, 0, len); //read up to len bytes
		            while (nrb != -1) {
		                baos.write(buffer, 0, nrb);
		                nrb = fis.read(buffer, 0, len);
		            }
		            buffer = baos.toByteArray();
		            fis.close();
	            }
	        } catch (FileNotFoundException e) {
	            e.printStackTrace();
	        } catch (IOException e) {
	            e.printStackTrace();
	        }
	    }
	    return buffer;
	}
	
	public Object readObjectFromStorage(String filename) {
	    Object obj = null;
	    //String packageName = this.getPackageName();

	    if (!isExternalStorageReadOnly()) {     
	        try {
	            File file = new File(this.path, filename);
	            if(file.exists()) {
		            FileInputStream fis = new FileInputStream(file);
		            ObjectInputStream in = new ObjectInputStream(fis);
		            obj = (Object)in.readObject();
		            in.close();
	            }
	        } catch(ClassNotFoundException e) {
	        	e.printStackTrace();
	        } catch (FileNotFoundException e) {
	            e.printStackTrace();
	        } catch (IOException e) {
	            e.printStackTrace();
	        }
	    }
	    return obj;
	}
	
	/**
	 * Delete external public file 
	 * @param filename - the filename to write to
	 */
	void deleteStorageFile(String filename) {
	    //String packageName = this.getPackageName();
	    File file = new File(this.path, filename);
	    if (file != null) {
	        file.delete();
	    }
	}
}
